# -*- coding: utf-8 -*-


# cmap2owl -- Helper application to convert from concept maps to OWL ontologies
# Copyright (c) 2008-2013  Rodrigo Rizzi Starr
#  
# Permission is hereby granted, free of charge, to any person obtaining a copy
# of this software and associated documentation files (the "Software"), to deal
# in the Software without restriction, including without limitation the rights
# to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
# copies of the Software, and to permit persons to whom the Software is
# furnished to do so, subject to the following conditions:
#  
# The above copyright notice and this permission notice shall be included in all
# copies or substantial portions of the Software.
#  
# THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
# IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
# FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
# AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
# LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
# OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
# SOFTWARE.


'''
This rule finds the domain and range of a relation

@author: Rodrigo Rizzi Starr
@copyright: Copyright © 2008-2013 Rodrigo Rizzi Starr
@license: MIT License
@contact: rodrigo.starr@gmail.com
'''


from infoProvider import InfoProvider, UnionOfInfoProviders
from mapperRule import MapperRule


class DomainRangeRule(MapperRule):
    "Identify the domain and range of a relation"
 
    def __init__(self, db):
          
        # Heuristics to identify relations
        rules = ["relationDomain(Relation, Cfrom) :- relationOWL(Relation),"
                      "fromPartRelation(Relation, Cfrom),"
                      "classOWL(Cfrom)",
                 "relationOWLDomain(Relation, Domain) :- "
                    "setof(Cfrom, relationDomain(Relation, Cfrom),"
                    "Domain)",
                    
                 "relationRange(Relation, Cto) :- relationOWL(Relation),"
                      "toPartRelation(Relation, Cto),"
                      "classOWL(Cto)",
                 "relationOWLRange(Relation, Range) :- "
                    "setof(Cto, relationRange(Relation, Cto),"
                    "Range)",
                    
                 "relationOWLIndividual(Relation, Ifrom, Ito) :- "
                    "relationOWL(Relation),"
                      "fromPartRelation(Relation, Ifrom),"
                      "individualOWL(Ifrom),"
                      "toPartRelation(Relation, Ito),"
                      "individualOWL(Ito)",
                    
                    ]
          
        MapperRule.__init__(self, "DomainsRanges", db, rules)

    def getQuestions(self):
        "This rule is completely automatic, so there are no questions"
        return []
      
    def getInfoProvider(self):
        "Returns an info provider about classes and individuals"
        
        domainProvider = InfoProvider(self.db,
                                     "relationOWLDomain(%s, Set)",
                                     "The domain of this relation is:")
        
        rangeProvider = InfoProvider(self.db,
                                     "relationOWLRange(%s, Set)",
                                     "The range of this relation is:")
        
        return UnionOfInfoProviders(domainProvider, rangeProvider)
